namespace SimpleWebServices.Models
{
    using System;
    using System.Globalization;

    /// http://en.wikipedia.org/wiki/ISO_4217
    public sealed class Money : ValueObject<Money>
    {
        public Money()
        {
            this.RegisterProperty(x => x.Amount);
            this.RegisterProperty(x => x.Currency);
        }

        public decimal Amount
        {
            get;
            set;
        }

        public Currency Currency
        {
            get;
            set;
        }

        public static implicit operator string(Money value)
        {
            return (null == value) ? null as string : value.ToString();
        }

        public static Money Parse(Currency currency, string value)
        {
            if (null == currency)
            {
                throw new ArgumentNullException("currency");
            }
            else if (null == value)
            {
                throw new ArgumentNullException("value");
            }
            else if (0 == value.Length)
            {
                throw new ArgumentOutOfRangeException("value");
            }

            return new Money
            {
                Amount = (decimal)double.Parse(value, NumberStyles.Currency, currency.ToNumberFormatInfo()),
                Currency = currency
            };
        }

        public override string ToString()
        {
            return this.ToString(this.Currency);
        }

        private string ToString(Currency currency)
        {
            if (null == currency)
            {
                throw new ArgumentNullException("currency");
            }

            return string.Format(currency.ToNumberFormatInfo(), "{0:C}", this.Amount);
        }
    }
}